package com.sunagy.demand.front.service.impl;

import com.sunagy.demand.front.VO.CustomerUserBindVo;
import com.sunagy.demand.front.config.MazConfig;
import com.sunagy.demand.front.dataobject.CustomerAuthToken;
import com.sunagy.demand.front.dataobject.CustomerUser;
import com.sunagy.demand.front.dto.CustomerUserDto;
import com.sunagy.demand.front.exception.*;
import com.sunagy.demand.front.repository.CustomerAuthTokenRepository;
import com.sunagy.demand.front.repository.CustomerUserRepository;
import com.sunagy.demand.front.security.SecurityUserDetails;
import com.sunagy.demand.front.service.CustomerAuthTokenService;
import com.sunagy.demand.front.service.CustomerUserInfoService;
import com.sunagy.demand.front.utils.EncryptUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;
import java.util.Optional;

/**
 * desc：#TODO fill me ！
 * author：三餘無夢生
 * date：2018/4/27
 * time：上午11:35
 */
@Service
public class CustomerAuthTokenServiceImpl implements CustomerAuthTokenService {
    @Autowired
    private MazConfig mazConfig;

    @Autowired
    private CustomerAuthTokenRepository customerAuthTokenRepository;

     @Autowired
    private CustomerUserRepository customerUserRepository;

     @Autowired
     private CustomerUserInfoService customerUserInfoService;



    @Override
    @Transactional
    public SecurityUserDetails validToken(String token) {
        SecurityUserDetails securityUserDetails = new SecurityUserDetails();
        CustomerAuthToken customerAuthToken = customerAuthTokenRepository.findByToken(token);
        if (customerAuthToken == null){
            throw new TokenNotFoundException();
        }
        if ((new Date()).compareTo(customerAuthToken.getToken_exptime()) > 0 ? true : false){
            throw new TokenExpiredException();
        }
        long currentTime = System.currentTimeMillis();
        currentTime +=mazConfig.getTokenExpireTime();
        Date date=new Date(currentTime);
        customerAuthToken.setToken_exptime(date);
        customerAuthTokenRepository.save(customerAuthToken);
        securityUserDetails.setUserId(customerAuthToken.getUserid());
        securityUserDetails.setToken(token);
        return securityUserDetails;
    }

    @Override
    @Transactional
    public String updateToken(CustomerUserDto customerUserDto) {
        long currentTime = System.currentTimeMillis();
        currentTime +=mazConfig.getTokenExpireTime();
        Date date=new Date(currentTime);
        CustomerAuthToken customerAuthToken = customerAuthTokenRepository.findByUserid(customerUserDto.getId());
        if (customerAuthToken == null){
            customerAuthToken = new CustomerAuthToken();
            customerAuthToken.setEnable(true);
            customerAuthToken.setUser_type(1);
            customerAuthToken.setUserid(customerUserDto.getId());
            String token = EncryptUtil.md5(customerUserDto.getId() + customerUserDto.getUsername() + customerUserDto.getPassword());
            customerAuthToken.setToken(token);
        }
        customerAuthToken.setToken_exptime(date);
        customerAuthTokenRepository.save(customerAuthToken);
        return customerAuthToken.getToken();
    }

    @Override
    @Transactional
    public String authWXMaOpenid(String openid) {
        long currentTime = System.currentTimeMillis();
        currentTime +=mazConfig.getTokenExpireTime();
        Date date=new Date(currentTime);
        String platform = "wechat";
        CustomerAuthToken customerAuthToken = customerAuthTokenRepository.findByOpenidAndPlatform(openid,platform);
        if (customerAuthToken == null){
            customerAuthToken = new CustomerAuthToken();
            customerAuthToken.setEnable(true);
            customerAuthToken.setUser_type(1);
            customerAuthToken.setOpenid(openid);
            customerAuthToken.setPlatform(platform);
        }else{
            if (customerAuthToken.getUserid() != null){
                CustomerUser customerUser = customerUserRepository.getOne(customerAuthToken.getUserid());
                String token = EncryptUtil.md5(customerUser.getId() + customerUser.getUsername() + customerUser.getPassword());
                customerAuthToken.setToken(token);
                customerAuthToken.setToken_exptime(date);
            }
        }
        customerAuthToken.setToken_exptime(date);
        customerAuthTokenRepository.save(customerAuthToken);
        return customerAuthToken.getToken();
    }

    @Override
    @Transactional
    public CustomerAuthToken bindMaOpenid(CustomerUserBindVo customerUserBindVo) {
        String platform = "wechat";
        CustomerAuthToken customerAuthToken = customerAuthTokenRepository.findByOpenidAndPlatform(customerUserBindVo.getOpenid(),platform);
        if (customerAuthToken == null){
            throw new OpenidNotFoundException();
        }
        if (customerAuthToken.getUserid() != null){
            throw new OpenidHasBindException();
        }

        CustomerUser customerUser = customerUserRepository.findByPhone(customerUserBindVo.getPhone());
        if (customerUser != null){
            customerAuthToken = customerAuthTokenRepository.findByUserid(customerUser.getId());
            if (customerAuthToken != null){
                throw new PhoneHasBindException();
            }else{
                customerAuthToken = new CustomerAuthToken();
            }
        }else{
            customerUser = new CustomerUser();
            customerUser.setPhone(customerUserBindVo.getPhone());
            customerUser.setUsername(customerUserBindVo.getPhone());
            customerUser.setEnable(true);
            customerUserRepository.save(customerUser);
        }
        customerAuthToken = bind(customerAuthToken,customerUserBindVo.getOpenid(),platform,customerUser);
        customerUserInfoService.add(customerUserBindVo,customerUser);
        return customerAuthToken;
    }

    private CustomerAuthToken bind(CustomerAuthToken customerAuthToken,String openid,String platform,CustomerUser customerUser) {
        long currentTime = System.currentTimeMillis();
        currentTime +=mazConfig.getTokenExpireTime();
        Date date=new Date(currentTime);
        customerAuthToken.setOpenid(openid);
        customerAuthToken.setUserid(customerUser.getId());
        customerAuthToken.setPlatform(platform);
        customerAuthToken.setEnable(true);
        customerAuthToken.setUser_type(1);
        String token = EncryptUtil.md5(customerUser.getId() + customerUser.getUsername() + customerUser.getPassword());
        customerAuthToken.setToken(token);
        customerAuthToken.setToken_exptime(date);
        customerAuthTokenRepository.save(customerAuthToken);
        return customerAuthToken;
    }

}
